home *** CD-ROM | disk | FTP | other *** search
/ Atari Mega Archive 1 / Atari Mega Archive - Volume 1.iso / mint / editors / mjovesrc.zoo / rec.c < prev    next >
C/C++ Source or Header  |  1992-04-04  |  4KB  |  187 lines

  1. /***************************************************************************
  2.  * This program is Copyright (C) 1986, 1987, 1988 by Jonathan Payne.  JOVE *
  3.  * is provided to you without charge, and with no warranty.  You may give  *
  4.  * away copies of JOVE, including sources, provided that this notice is    *
  5.  * included in all the files.                                              *
  6.  ***************************************************************************/
  7.  
  8. #include "jove.h"
  9. #include "fp.h"
  10. #include "rec.h"
  11.  
  12. #ifndef    MAC
  13. #    include <sys/file.h>
  14. #endif
  15.  
  16. private int    rec_fd = -1;
  17. private char    *recfname;
  18. private File    *rec_out;
  19.  
  20. #ifndef    L_SET
  21. #    define L_SET 0
  22. #endif
  23.  
  24. private struct rec_head    Header;
  25.  
  26. private void
  27. recinit()
  28. {
  29.     char    buf[128];
  30.  
  31. #ifdef    MAC
  32.     swritef(buf, sizeof(buf), "%s/%s", HomeDir, p_tempfile);
  33. #else
  34.     swritef(buf, sizeof(buf), "%s/%s", TmpFilePath, p_tempfile);
  35. #endif
  36.     recfname = copystr(buf);
  37.     recfname = mktemp(recfname);
  38.     rec_fd = creat(recfname, 0644);
  39.     if (rec_fd == -1) {
  40.         complain("Cannot create \"%s\"; recovery disabled.", recfname);
  41.         return;
  42.     }
  43.     /* initialize the record IO */
  44.     rec_out = fd_open(recfname, F_WRITE|F_LOCKED, rec_fd, iobuff, LBSIZE);
  45.  
  46.     /* Initialize the record header. */
  47.     Header.Uid = getuid();
  48.     Header.Pid = getpid();
  49.     Header.UpdTime = 0L;
  50.     Header.Nbuffers = 0;
  51.     (void) write(rec_fd, (UnivPtr) &Header, sizeof Header);
  52. }
  53.  
  54. /* Close recfile before execing a child process.
  55.  * Since we might be vforking, we must not change any variables
  56.  * (in particular rec_fd).
  57.  */
  58. void
  59. recclose()
  60. {
  61.     if (rec_fd == -1)
  62.         return;
  63.     (void) close(rec_fd);
  64. }
  65.  
  66. /* Close and remove recfile before exiting. */
  67.  
  68.  
  69. void
  70. recremove()
  71. {
  72.     if (rec_fd == -1)
  73.         return;
  74.     recclose();
  75.     (void) unlink(recfname);
  76. }
  77.  
  78. private void
  79. putaddr(addr, p)
  80. daddr    addr;
  81. register File    *p;
  82. {
  83.     register char    *cp = (char *) &addr;
  84.     register int    nchars = sizeof (daddr);
  85.  
  86.     while (--nchars >= 0)
  87.         jputc(*cp++ & 0377, p);
  88. }
  89.  
  90. private void
  91. putn(cp, nbytes)
  92. register char    *cp;
  93. register size_t    nbytes;
  94. {
  95.     while (nbytes-- > 0)
  96.         jputc(*cp++ & 0377, rec_out);
  97. }
  98.  
  99. /* Write out the line pointers for buffer B. */
  100.  
  101. private void
  102. dmppntrs(b)
  103. register Buffer    *b;
  104. {
  105.     register Line    *lp;
  106.  
  107.     for (lp = b->b_first; lp != NULL; lp = lp->l_next)
  108.         putaddr(lp->l_dline, rec_out);
  109. }
  110.  
  111. /* dump the buffer info and then the actual line pointers. */
  112.  
  113. private void
  114. dmp_buf_header(b)
  115. register Buffer    *b;
  116. {
  117.     struct rec_entry    record;
  118.     register Line    *lp;
  119.     register int    nlines = 0;
  120.  
  121.     for (lp = b->b_first; lp != NULL; lp = lp->l_next, nlines++)
  122.         if (lp == b->b_dot)
  123.             record.r_dotline = nlines;
  124.     strcpy(record.r_fname, b->b_fname ? b->b_fname : NullStr);
  125.     strcpy(record.r_bname, b->b_name);
  126.     record.r_nlines = nlines;
  127.     record.r_dotchar = b->b_char;
  128.     putn((char *) &record, sizeof record);
  129. }
  130.  
  131. /* Goes through all the buffers and syncs them to the disk. */
  132.  
  133. int    SyncFreq = 50;
  134.  
  135. void
  136. SyncRec()
  137. {
  138.     register Buffer    *b;
  139.     static bool    beenhere = NO;
  140.  
  141.     if (!beenhere) {
  142.         beenhere = YES;
  143.         recinit();    /* Init recover file. */
  144.     }
  145.     if (rec_fd == -1)
  146.         return;
  147.     lseek(rec_fd, 0L, L_SET);
  148.     (void) time(&Header.UpdTime);
  149.     Header.Nbuffers = 0;
  150.     for (b = world; b != NULL; b = b->b_next)
  151.         if (b->b_type == B_SCRATCH || !IsModified(b))
  152.             continue;
  153.         else
  154.             Header.Nbuffers += 1;
  155.     Header.FreePtr = DFree;
  156.     putn((char *) &Header, sizeof Header);
  157.     if (Header.Nbuffers != 0) {
  158.         lsave();    /* this makes things really right */
  159.         SyncTmp();
  160.         for (b = world; b != NULL; b = b->b_next)
  161.             if (b->b_type == B_SCRATCH || !IsModified(b))
  162.                 continue;
  163.             else
  164.                 dmp_buf_header(b);
  165.         for (b = world; b != NULL; b = b->b_next)
  166.             if (b->b_type == B_SCRATCH || !IsModified(b))
  167.                 continue;
  168.             else
  169.                 dmppntrs(b);
  170.     }
  171.     flushout(rec_out);
  172. }
  173.  
  174. /* Full Recover.  What we have to do is go find the name of the tmp
  175.    file data/rec pair and use those instead of the ones we would have
  176.    created eventually.  The rec file has a list of buffers, and then
  177.    the actual pointers.  Stored for each buffer is the buffer name,
  178.    the file name, the number of lines, the current line, the current
  179.    character.  The current modes do not need saving as they will be
  180.    saved when the file name is set.  If a process was running in a
  181.    buffer, it will be lost. */
  182.  
  183. void
  184. FullRecover()
  185. {
  186. }
  187.